package com.fetch;

import java.io.File;
import java.util.Collections;
import java.util.Map;
import java.util.WeakHashMap;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import android.content.Context;
import android.os.Handler;

import com.dstats.R;

public abstract class Loader <K,L,T> {
    
    MemoryCache <K, L> memoryCache=new MemoryCache<K, L>();
    FileCache fileCache;
    private Map<T, K> imageViews=Collections.synchronizedMap(new WeakHashMap<T, K>());
    ExecutorService executorService;
    Handler handler=new Handler();//handler to display images in UI thread
    
    public Loader(Context context){
        fileCache=new FileCache(context);
        executorService=Executors.newFixedThreadPool(5);
    }
    
    final int stub_id=R.drawable.white;
    
    public abstract void Display(K url, T imageView);
    
        
    protected void queuePhoto(K url, T imageView)
    {
        ToLoad p=new ToLoad(url, imageView);
        executorService.submit(new ThingsLoader(p));
    }
    
    protected abstract L getObject(K url) ;

    //decodes image and scales it to reduce memory consumption
    protected abstract L decodeFile(File f);
    
    //Task for the queue
    protected class ToLoad
    {
        public K url;
        public T imageView;
        public ToLoad(K u, T i){
            url=u; 
            imageView=i;
        }
    }
    
    class ThingsLoader implements Runnable {
        ToLoad thingToLoad;
        ThingsLoader(ToLoad photoToLoad){
            this.thingToLoad=photoToLoad;
        }
        
        @Override
        public void run() {
            try{
                if(imageViewReused(thingToLoad))
                    return;
                L bmp=getObject(thingToLoad.url);
                memoryCache.put(thingToLoad.url, bmp);
                if(imageViewReused(thingToLoad))
                    return;
                BitmapDisplayer bd=new BitmapDisplayer(bmp, thingToLoad);
                handler.post(bd);
            }catch(Throwable th){
                th.printStackTrace();
            }
        }
    }
    
    boolean imageViewReused(ToLoad photoToLoad){
        K tag=imageViews.get(photoToLoad.imageView);
        if(tag==null || !tag.equals(photoToLoad.url))
            return true;
        return false;
    }
    
    //Used to display bitmap in the UI thread
    class BitmapDisplayer implements Runnable
    {

		L bitmap;
        ToLoad photoToLoad;
        public BitmapDisplayer(L b, ToLoad p){bitmap=b;photoToLoad=p;}
        public void run()
        {
            if(imageViewReused(photoToLoad))
                return;
            if(bitmap!=null){
            	// TODO 
            }
            else {
            	// TODO
            }
        }
    }

    public void clearCache() {
        memoryCache.clear();
        fileCache.clear();
    }

}
